// Project name:JavaRedis
// Creator:muhong
// Date time:2022/12/17,12:47 下午
// Name:DefaultThreadFactory

package org.gmh.util.concurrent;

import java.util.concurrent.ThreadFactory;
import java.util.concurrent.atomic.AtomicInteger;

public class DefaultThreadFactory implements ThreadFactory {

    private static final AtomicInteger poolId = new AtomicInteger();
    private final AtomicInteger nextId = new AtomicInteger();
    private final String prefix;
    private final boolean daemon;
    private final int priority;
    protected final ThreadGroup threadGroup;

    public DefaultThreadFactory(Class<?> poolType) {
        this(toPoolName(poolType), false, Thread.NORM_PRIORITY, System.getSecurityManager() == null ?
                Thread.currentThread().getThreadGroup() : System.getSecurityManager().getThreadGroup());
    }

    public DefaultThreadFactory(String poolName, boolean daemon, int priority, ThreadGroup threadGroup) {

        if (poolName == null) {
            throw new NullPointerException("pool name");
        }
        if (priority > Thread.MAX_PRIORITY || priority < Thread.MIN_PRIORITY) {
            throw new IllegalArgumentException("priority:" + priority);
        }
        prefix = poolName + "-" + poolId.incrementAndGet() + "-";
        this.daemon = daemon;
        this.priority = priority;
        this.threadGroup = threadGroup;
    }

    public static String toPoolName(Class<?> poolType) {
        if (poolType == null) {
            throw new NullPointerException("pool type");
        }
        return poolType.getName();
    }

    @Override
    public Thread newThread(Runnable r) {
        Thread thread = newThread(FastThreadLocalRunnable.wrap(r), prefix + nextId.incrementAndGet());
//        thread.setName(prefix + poolId.incrementAndGet());
        if (thread.isDaemon() != daemon) {
            thread.setDaemon(daemon);
        }
        if (thread.getPriority() != priority) {
            thread.setPriority(priority);
        }
        return thread;
    }

    protected Thread newThread(Runnable r, String name) {
        return new FastThreadLocalThread(threadGroup, r, name);
    }
}
